package com.loper7.base.ui;

import android.annotation.TargetApi;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.PixelFormat;
import android.net.Uri;
import android.text.TextUtils;
import android.util.Log;
import android.view.KeyEvent;
import android.view.View;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.widget.LinearLayout;

import com.kingja.loadsir.callback.Callback;
import com.kingja.loadsir.core.LoadService;
import com.kingja.loadsir.core.LoadSir;
import com.loper7.base.R;
import com.loper7.base.utils.BackHelper;
import com.loper7.base.utils.Logger;
import com.loper7.base.utils.loadsir.PlaceholderDetailsCallback;
import com.loper7.base.utils.loadsir.TimeoutCallback;
import com.loper7.base.widget.bestwebview.SonicRuntimeImpl;
import com.loper7.base.widget.bestwebview.SonicSessionClientImpl;
import com.loper7.base.widget.bestwebview.X5WebView;
import com.loper7.layout.TitleBar;
import com.tencent.smtt.export.external.interfaces.SslError;
import com.tencent.smtt.export.external.interfaces.SslErrorHandler;
import com.tencent.smtt.export.external.interfaces.WebResourceError;
import com.tencent.smtt.export.external.interfaces.WebResourceRequest;
import com.tencent.smtt.export.external.interfaces.WebResourceResponse;
import com.tencent.smtt.sdk.DownloadListener;
import com.tencent.smtt.sdk.TbsVideo;
import com.tencent.smtt.sdk.WebChromeClient;
import com.tencent.smtt.sdk.WebView;
import com.tencent.smtt.sdk.WebViewClient;
import com.tencent.sonic.sdk.SonicConfig;
import com.tencent.sonic.sdk.SonicEngine;
import com.tencent.sonic.sdk.SonicSession;
import com.tencent.sonic.sdk.SonicSessionConfig;

import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.List;

/**
 * @author LOPER7
 * @date 2018/12/13 17:32
 * @Description:
 */
public class BestWebActivity extends BaseActivity {

    private LinearLayout webFrame;
    private TitleBar titleBar;
    private SonicSession sonicSession;
    private SonicSessionClientImpl sonicSessionClient;
    private X5WebView webView;
    private String url = "";
    private String htmlData = "";
    private String title;
    private LoadService loadService;
    private boolean isRedirect = false; //是否是重定向
    private boolean isPageOk = false; //目的地地址加载完成

    @Override
    protected int getContentViewId() {
        getWindow().addFlags(WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED);
        getWindow().setFormat(PixelFormat.TRANSLUCENT);
        // init sonic engine if necessary, or maybe u can do this when application created
        if (!SonicEngine.isGetInstanceAllowed()) {
            SonicEngine.createInstance(new SonicRuntimeImpl(getApplication()), new SonicConfig.Builder().build());
        }

        url = getIntent().getStringExtra("url");
        htmlData = getIntent().getStringExtra("htmlData");
        title = getIntent().getStringExtra("title");

        // if it's sonic mode , startup sonic session at first time
        SonicSessionConfig.Builder sessionConfigBuilder = new SonicSessionConfig.Builder();
        sessionConfigBuilder.setSupportLocalServer(true);

        sonicSessionClient = null;
        // create sonic session and run sonic flow
        sonicSession = SonicEngine.getInstance().createSession(url, sessionConfigBuilder.build());
        if (null != sonicSession) {
            sonicSession.bindClient(sonicSessionClient = new SonicSessionClientImpl());
        }

        return R.layout.activity_web;
    }

    @Override
    protected void initData() {


    }

    @Override
    protected void initView() {
        webFrame = findViewById(R.id.web_frame);
        titleBar = findViewById(R.id.titleBar);

        webView = new X5WebView(this);
        LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
        webView.setLayoutParams(layoutParams);
        webView.setWebViewClient(webViewClient);
        webView.setWebChromeClient(webChromeClient);
        webView.setDownloadListener(downloadListener);

        webFrame.addView(webView);

        if (!TextUtils.isEmpty(url)) {
            if (sonicSessionClient != null) {
                sonicSessionClient.bindWebView(webView);
                sonicSessionClient.clientReady();
            } else { // default mode
                webView.loadUrl(url);
            }
        } else {
            webView.loadDataWithBaseURL("android://", htmlData, "text/html", "utf-8", null);
        }

        loadService = LoadSir.getDefault().register(webView, new Callback.OnReloadListener() {
            @Override
            public void onReload(View v) {
                loadService.showCallback(PlaceholderDetailsCallback.class);
                if (sonicSession != null)
                    sonicSession.refresh();
                else
                    webView.reload();
            }
        });
        loadService.showCallback(PlaceholderDetailsCallback.class);
    }

    @Override
    protected void initListener() {

        titleBar.setOnBackListener(new TitleBar.OnBackListener() {
            @Override
            public void onBackClick() {
                if (webView.canGoBack())
                    webView.goBack();
                else
                    backHelper.backward();
            }
        });
    }


    @Override
    protected void onDestroy() {
        if (null != sonicSession) {
            sonicSession.destroy();
            sonicSession = null;
        }
        super.onDestroy();
    }

    @Override
    public void onBackPressed() {
        if (webView.canGoBack())
            webView.goBack();
        else
            super.onBackPressed();
    }

    private WebViewClient webViewClient = new WebViewClient() {

        @Override
        public boolean shouldOverrideUrlLoading(WebView view, String url) {
            if (TextUtils.isEmpty(url))
                return true;
            if (url.startsWith("http")) {
                isRedirect = false;
                if (isPageOk) {
                    getBuilder(backHelper).setUrl(url).start();
                    return true;
                }
                return false;
            } else
                return super.shouldOverrideUrlLoading(view, url);
        }

        @Override
        public void onPageStarted(WebView webView, String s, Bitmap bitmap) {
            super.onPageStarted(webView, s, bitmap);
            isRedirect = true;
            isPageOk = false;
        }

        @Override
        public void onPageFinished(WebView view, String url) {
            super.onPageFinished(view, url);
            isPageOk = isRedirect;
            if (sonicSession != null) {
                sonicSession.getSessionClient().pageFinish(url);
            }
            loadService.showSuccess();
        }

        @Override
        public void onReceivedError(WebView webView, int i, String s, String s1) {
            super.onReceivedError(webView, i, s, s1);
            loadService.showCallback(TimeoutCallback.class);
        }

        @Override
        public void onReceivedError(WebView webView, WebResourceRequest webResourceRequest, WebResourceError webResourceError) {
            super.onReceivedError(webView, webResourceRequest, webResourceError);
            if (webResourceRequest.isForMainFrame())
                loadService.showCallback(TimeoutCallback.class);
        }

        @TargetApi(21)
        public WebResourceResponse shouldInterceptRequest(WebView view, WebResourceRequest
                request) {
            return shouldInterceptRequest(view, request.getUrl().toString());
        }

        @Override
        public WebResourceResponse shouldInterceptRequest(WebView view, String url) {
            if (sonicSession != null) {
                return (WebResourceResponse) sonicSession.getSessionClient().requestResource(url);
            }
            return null;
        }

        @Override
        public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
            handler.proceed();  // 接受所有网站的证书
        }
    };

    private WebChromeClient webChromeClient = new WebChromeClient() {
        @Override
        public void onReceivedTitle(WebView webView, String s) {
            super.onReceivedTitle(webView, s);
            if (TextUtils.isEmpty(title))
                titleBar.setTitleText(s);
            else
                titleBar.setTitleText(title);
        }
    };

    private DownloadListener downloadListener = new DownloadListener() {
        @Override
        public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimeType, long contentLength) {
            Intent intent = new Intent(Intent.ACTION_VIEW);
            intent.addCategory(Intent.CATEGORY_BROWSABLE);
            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            intent.setData(Uri.parse(url));
            startActivity(intent);
        }
    };


    public static Builder getBuilder(Context context) {
        return new Builder(context);
    }

    public static Builder getBuilder(BackHelper BackHelper) {
        return new Builder(BackHelper);
    }


    public static class Builder {
        private String url;
        private String htmlData;
        private String title;
        private Context context;
        private BackHelper backHelper;
        private Intent intent;

        public Builder(Context context) {
            this.context = context;
        }

        public Builder(BackHelper backHelper) {
            this.backHelper = backHelper;
            this.context = backHelper.getContext();
        }

        public Builder setUrl(String url) {
            this.url = url;
            return this;
        }

        public Builder setHtmlData(String htmlData) {
            this.htmlData = htmlData;
            return this;
        }

        public Builder setTitle(String title) {
            this.title = title;
            return this;
        }

        public void start() {
            intent = new Intent(context, BestWebActivity.class);
            intent.putExtra("url", url);
            intent.putExtra("htmlData", htmlData);
            intent.putExtra("title", title);

            if (backHelper == null)
                context.startActivity(intent);
            else
                backHelper.forward(intent);
        }
    }


}
